package com.firexxx.study.lock.scene;

import com.firexxx.study.asyncservlet.task.AsyncServletTask;
import com.firexxx.study.lock.task.AtomicConsumeTask;
import com.firexxx.study.lock.task.LockConsumeTask;
import com.firexxx.study.lock.task.NullConsumeTask;
import com.firexxx.study.lock.task.SyncConsumeTask;
import com.firexxx.study.performancetest.scene.*;
import com.firexxx.study.performancetest.task.IFixedTimeConsumeTask;
import com.firexxx.study.performancetest.task.rest.RestArg;
import com.firexxx.study.performancetest.timeconsume.ConsumeTaskType;
import com.firexxx.study.performancetest.timeconsume.ConsumeTimeArg;

import java.util.ArrayList;
import java.util.List;

/**
 * 多个线程同时执行一个任务，来竞争锁资源
 *
 * @author fireXXX
 * @date 2020/11/19 0:27
 **/
public class TestScene {

    private IFixedTimeConsumeTask nullTask = new NullConsumeTask();
    private IFixedTimeConsumeTask syncTask = new SyncConsumeTask();
    private IFixedTimeConsumeTask lockTask = new LockConsumeTask();
    private IFixedTimeConsumeTask atomicTask = new AtomicConsumeTask();

    public MultiResult start(int thread, int sleepTime, ConsumeTaskType consumeTaskType, int sample) throws InterruptedException {
        MultiResult multiResult = new MultiResult();

        ConsumeTimeArg arg = new ConsumeTimeArg(sleepTime, consumeTaskType);
        nullTask.init(arg);
        syncTask.init(arg);
        lockTask.init(arg);
        atomicTask.init(arg);

        for (int i=0; i<thread; i++) {
            new Thread(nullTask).start();
        }

        for (int i=0; i<thread; i++) {
            new Thread(syncTask).start();
        }

        for (int i=0; i<thread; i++) {
            new Thread(lockTask).start();
        }

        for (int i=0; i<thread; i++) {
            new Thread(atomicTask).start();
        }

        String pre = thread + "-" + sleepTime + "-" + consumeTaskType + "-";
        SingleResult nullResult = new SingleResult(pre + "null");
        SingleResult syncResult = new SingleResult(pre + "sync");
        SingleResult lockResult = new SingleResult(pre + "lock");
        SingleResult atomicResult = new SingleResult(pre + "atomic");
        multiResult.getData().add(nullResult);
        multiResult.getData().add(syncResult);
        multiResult.getData().add(lockResult);
        multiResult.getData().add(atomicResult);

        int count = sample;
        for (int i=0; i<count; i++) {
            Thread.sleep(1000);

            nullResult.getData().add(nullTask.getCount());
            syncResult.getData().add(syncTask.getCount());
            lockResult.getData().add(lockTask.getCount());
            atomicResult.getData().add(atomicTask.getCount());

            System.out.println("null : " + nullTask.getCount());
            System.out.println("sync : " + syncTask.getCount());
            System.out.println("lock : " + lockTask.getCount());
            System.out.println("atomic : " + atomicTask.getCount());
            System.out.println();
        }

        nullTask.stop();
        syncTask.stop();
        lockTask.stop();
        atomicTask.stop();

        return multiResult;
    }

}